package me.ivenapp.gomoku.slice;

import com.hjq.permissions.OnPermission;
import com.hjq.permissions.XXPermissions;
import com.lxj.xpopup.XPopup;
import com.lxj.xpopup.impl.ConfirmPopupView;
import me.ivenapp.gomoku.GomokuAbility;
import me.ivenapp.gomoku.IntentBuilder;
import me.ivenapp.gomoku.ResourceTable;
import me.ivenapp.gomoku.SliceBase;
import me.ivenapp.gomoku.component.GomokuBoard;
import me.ivenapp.gomoku.component.TitleBar;
import ohos.aafwk.ability.continuation.*;
import ohos.aafwk.content.Intent;
import ohos.agp.components.AttrHelper;
import ohos.agp.components.Text;
import ohos.agp.components.element.Element;
import ohos.agp.components.element.VectorElement;
import ohos.agp.utils.TextAlignment;
import ohos.hiviewdfx.HiLog;
import ohos.hiviewdfx.HiLogLabel;
import ohos.system.DeviceInfo;
import java.util.List;

import static ohos.security.SystemPermission.DISTRIBUTED_DATASYNC;

public class GomokuModeSlice extends SliceBase {
    private static final HiLogLabel TAG = new HiLogLabel(HiLog.LOG_APP, 0x1001, GomokuModeSlice.class.getSimpleName());

    @Override
    protected void onStart(Intent intent) {
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_slice_gomoku_mode);

        initUI();
    }

    protected void initUI() {
        TitleBar titleBar = (TitleBar) findComponentById(ResourceTable.Id_title_bar);
        titleBar.addActionIcon(new Element[] { new VectorElement(this, ResourceTable.Graphic_ic_public_more_filled)}, (component, i) -> {
            if(i == 0) {
                new XPopup.Builder(getContext())
                        .atView(component)
                        .asAttachList(new String[]{ "玩法帮助"}, null, (i1, s) -> {
                            if(i1 == 0) {
                                showHelper();
                            }
                        }).show();
            }
        });

        int rowNum = 10;
        if("tablet".equals(DeviceInfo.getDeviceType())) {
            rowNum = 15;
        }

        //人机对战按钮
        int finalRowNum = rowNum;
        findComponentById(ResourceTable.Id_btn_mode_ai).setClickedListener(component -> {
            startGame(GomokuBoard.MODE_AI, 0,"电脑", finalRowNum);
        });

        //联机对战按钮
        findComponentById(ResourceTable.Id_btn_mode_online).setClickedListener(component -> {
            XXPermissions.with(getAbility())
                    .permission(DISTRIBUTED_DATASYNC)
                    .request(new OnPermission() {
                        @Override
                        public void hasPermission(List<String> granted, boolean all) {
                            if (all) {
                                registerContinuationService();
                            }
                        }

                        @Override
                        public void noPermission(List<String> denied, boolean never) {
                            if (never) {
                                // 如果是被永久拒绝就跳转到应用权限系统设置页面
                                new XPopup.Builder(getContext())
                                        .isDestroyOnDismiss(true)
                                        .asConfirm("获取权限失败", "联机对战需要开启【多设备协同】权限", "取消", "去开启", () -> {
                                            String[] permissions = new String[denied.size()];
                                            denied.toArray(permissions);
                                            XXPermissions.startPermissionActivity(GomokuModeSlice.this, permissions, this);
                                        }, null, false)
                                        .show();
                            }
                        }
                    });
        });

        //自娱自乐按钮
        findComponentById(ResourceTable.Id_btn_mode_self).setClickedListener(component -> {
            startGame(GomokuBoard.MODE_SELF, 0, "自己", finalRowNum);
        });
    }

    private void showHelper(){
        String strHelp = "联机对战需要两台设备登录同一华为帐号并打开WIFI和蓝牙。";
        ConfirmPopupView view = new XPopup.Builder(this)
                .asConfirm("玩法帮助", strHelp, "取消", null, null, null, true);
        Text text = view.getContentTextView();
        text.setTextSize(AttrHelper.fp2px(14, this));
        text.setTextAlignment(TextAlignment.LEFT);
        view.show();
    }

    //分布式联机相关-->

    // 注册流转任务管理服务后返回的Ability token
    private int abilityToken;
    //选择的设备信息
    private ContinuationDeviceInfo mDeviceInfo;
    private IContinuationRegisterManager continuationRegisterManager;
    // 连接设备状态变更的回调
    private final IContinuationDeviceCallback deviceCallback = new IContinuationDeviceCallback() {
        @Override
        public void onConnected(ContinuationDeviceInfo deviceInfo) {
            HiLog.debug(TAG, "onConnected. deviceId=" + deviceInfo.getDeviceId() + ", deviceName=" + deviceInfo.getDeviceName());
            mDeviceInfo = deviceInfo;
            //更新连接状态
            getUITaskDispatcher().syncDispatch(() -> {
                if(continuationRegisterManager != null) {
                    continuationRegisterManager.updateConnectStatus(abilityToken, mDeviceInfo.getDeviceId(), DeviceConnectState.CONNECTED.getState(), null);
                }
            });
            startRemoteFa();
        }

        @Override
        public void onDisconnected(String deviceId) {
            HiLog.debug(TAG, "onDisconnected. deviceId=" + deviceId);
            getUITaskDispatcher().asyncDispatch(() -> {
                continuationRegisterManager.updateConnectStatus(abilityToken, mDeviceInfo.getDeviceId(),
                        DeviceConnectState.IDLE.getState(), i -> {
                            HiLog.debug(TAG, "onDisconnected->updateConnectStatus idle. i=" + i);
                        });
                mDeviceInfo = null;
            });
        }

        @Override
        public void onDeviceConnectDone(String s, String s1) {}

        @Override
        public void onDeviceDisconnectDone(String s) {}
    };
    // 注册FA流转管理服务的回调
    private final RequestCallback registerCallback = new RequestCallback() {
        @Override
        public void onResult(int result) {
            abilityToken = result;
            showDevicesDialog();
        }
    };
    /**
     * 注册流转服务
     */
    private void registerContinuationService() {
        continuationRegisterManager = getContinuationRegisterManager();
        continuationRegisterManager.register(getBundleName(), getJsonParams(), deviceCallback, registerCallback);
    }

    // 解注册流转任务管理服务
    private void unRegisterContinuationService() {
        if(continuationRegisterManager != null) {
//            HiLog.debug(TAG, "unRegisterContinuationService");
            continuationRegisterManager.unregister(abilityToken, i -> {
                //i=0，解注册成功。i=-1：解注册失败
                HiLog.debug(TAG, "unregister callback: i=" + i);
            });
            //终端与流转服务的连接
            continuationRegisterManager.disconnect();
        }
    }

    /**
     * 显示设备选择对话框
     */
    private void showDevicesDialog() {
        HiLog.debug(TAG, "showDevicesDialog: abilityToken=" + abilityToken);
        continuationRegisterManager.showDeviceList(abilityToken, getJsonParams(), result -> HiLog.debug(TAG, "show devices success"));
    }

    private ExtraParams getJsonParams() {
        ExtraParams extraParams = new ExtraParams();
        extraParams.setDevType(new String[]{ ExtraParams.DEVICETYPE_SMART_PHONE, ExtraParams.DEVICETYPE_SMART_PAD });
        extraParams.setDescription("支持手机和平板设备");
//        String jsParams =  "{'filter':{'commonFilter':{'system':{'harmonyVersion':'2.0.0'},'groupType':'1|256','faFilter':'{\"localVersionCode\":1004000,\"localMinCompatibleVersionCode\":1004000,\"targetBundleName\": \"me.ivenapp.toolbox\"}'}},'transferScene':0}";
        String jsParams =  "{'filter':{'commonFilter':{'system':{'harmonyVersion':'2.0.0'},'groupType':'1|256'}},'transferScene':0}";
        extraParams.setJsonParams(jsParams);
        return extraParams;
    }

    /**
     * 启动远程FA
     */
    private void startRemoteFa() {
        if(mDeviceInfo != null) {
            long gameId = System.currentTimeMillis();
            int rowNum = 10;
            if("tablet".equals(DeviceInfo.getDeviceType()) && DeviceInfo.getDeviceType().equals(mDeviceInfo.getDeviceType())) {
                //如果两台设备都是平板，棋盘规格设置为 15x15
                rowNum = 15;
            }

            IntentBuilder intentBuilder = new IntentBuilder(this);
            intentBuilder.withDeviceId(mDeviceInfo.getDeviceId())
                    .withAbility(GomokuAbility.class)
                    .withBundleName(getBundleName())
                    .withFlags(Intent.FLAG_ABILITYSLICE_MULTI_DEVICE | Intent.FLAG_ABILITY_NEW_MISSION | Intent.FLAG_ABILITY_CLEAR_MISSION)
                    .setParam(GomokuBoard.PARAM_GAME_MODE, GomokuBoard.MODE_ONLINE)
                    .setParam(GomokuBoard.PARAM_PIECE_TYPE, GomokuBoard.PIECE_TYPE_BLACK)
                    .setParam(GomokuBoard.PARAM_OPPONENT, "对方")
                    .setParam(GomokuAbilitySlice.PARAM_ROW_NUM, rowNum)
                    .setParam("gameId", gameId)
                    .goAbility();
            startGame(GomokuBoard.MODE_ONLINE, gameId,  "对方", rowNum);
        }
    }

    @Override
    protected void onResult(int requestCode, Intent resultData) {
        HiLog.debug(TAG, "onResult");
        if(continuationRegisterManager != null) {
            continuationRegisterManager.updateConnectStatus(abilityToken, mDeviceInfo.getDeviceId(),
                    DeviceConnectState.IDLE.getState(), i -> {
                        HiLog.debug(TAG, "onDisconnected->updateConnectStatus idle. i=" + i);
                    });
        }
    }

    /**
     * 启动本地游戏
     * @param mode
     */
    private void startGame(int mode, long gameId,  String opponent, int rowNum) {
        Intent intent = new Intent();
        intent.setParam(GomokuBoard.PARAM_GAME_MODE, mode);
        intent.setParam(GomokuBoard.PARAM_PIECE_TYPE, GomokuBoard.PIECE_TYPE_WHITE);
        intent.setParam(GomokuBoard.PARAM_OPPONENT, opponent);
        intent.setParam(GomokuAbilitySlice.PARAM_ROW_NUM, rowNum);
        intent.setParam("gameId", gameId);
        presentForResult(new GomokuAbilitySlice(), intent, 0x1400);
    }

    @Override
    protected void onStop() {
        super.onStop();
        unRegisterContinuationService();
    }
}
